package com.renchunlin.qqstepview

import android.content.Context
import android.graphics.*
import android.util.AttributeSet
import android.util.Log
import android.util.TypedValue
import android.view.View

/*
 * class title: 
 * Author by RenChunLin, Email 18957806320@163.com, Date on 2021/5/17.
 * PS: Not easy to write code, please indicate.
 */
class QQStepView : View {

    private var mOuterColor = Color.RED
    private var mInnerColor = Color.BLUE
    private var mBorderWidth = 10f
    private var mStepTextSize = 16
    private var mStepTextColor = Color.RED
    private var rectF: RectF

    //外圆画笔
    private var mOutPaint: Paint

    //内圆画笔
    private var mInnerPaint: Paint

    //文字画笔
    private var mTextPaint: Paint

    private var mStepMax = 0

    //当前步数
    private var mCurrentStep = 0

    private val textBound: Rect

    constructor(context: Context) : this(context, null)

    constructor(context: Context, attrs: AttributeSet?) : this(context, attrs, 0)

    constructor(context: Context, attrs: AttributeSet?, defStyleAttr: Int) : super(
        context,
        attrs,
        defStyleAttr
    ) {
        val typedArray = context.obtainStyledAttributes(attrs, R.styleable.QQStepView)

        mOuterColor = typedArray.getColor(R.styleable.QQStepView_outerColor, mOuterColor)
        mInnerColor = typedArray.getColor(R.styleable.QQStepView_innerColor, mInnerColor)
        mBorderWidth = typedArray.getDimension(
            R.styleable.QQStepView_borderWidth,
            TypedValue.applyDimension(
                TypedValue.COMPLEX_UNIT_DIP,
                mBorderWidth,
                resources.displayMetrics
            )
        )

        mStepTextSize =
            typedArray.getDimensionPixelSize(
                R.styleable.QQStepView_stepTextSize,
                TypedValue.applyDimension(
                    TypedValue.COMPLEX_UNIT_SP,
                    mStepTextSize.toFloat(),
                    resources.displayMetrics
                ).toInt()
            )

        mStepTextColor = typedArray.getColor(R.styleable.QQStepView_stepTextColor, mStepTextColor)

        typedArray.recycle()

        rectF = RectF()
        mOutPaint = Paint()
        mInnerPaint = Paint()
        mTextPaint = Paint()
        textBound = Rect()
    }

    override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec)
        //调用者在布局文件中可能 wrap_content
        //获取模式 AT_MOST 默认为80dp

        //高度宽度不一致 取最小值，确保是个正方形
        val widthMode = MeasureSpec.getMode(widthMeasureSpec)
        val heightMode = MeasureSpec.getMode(heightMeasureSpec)

        val widthSize = MeasureSpec.getSize(widthMeasureSpec)
        val heightSize = MeasureSpec.getSize(heightMeasureSpec)

        if (widthMode == MeasureSpec.EXACTLY && heightMode == MeasureSpec.EXACTLY) {
            setMeasuredDimension(
                if (widthSize > heightSize) widthSize else heightSize,
                if (widthSize > heightSize) widthSize else heightSize
            )
        } else {
            setMeasuredDimension(150, 150)
        }
    }

    override fun onDraw(canvas: Canvas?) {
        super.onDraw(canvas)
        //画外圆弧
        val center = measuredWidth / 2
        val radius = center - mBorderWidth / 2
        Log.i("chen", "center: $center")
        Log.i("chen", "radius: $radius")
        Log.i("chen", "center-radius: ${center - radius}")
        Log.i("chen", "center-radius: ${center + radius}")

        rectF.set(center - radius, center - radius, center + radius, center + radius)

        /**
         * 外圆
         */
        mOutPaint.isAntiAlias = true
        mOutPaint.strokeWidth = mBorderWidth
        mOutPaint.color = mOuterColor
        //设置空心
        mOutPaint.style = Paint.Style.STROKE
        //设置圆弧start 和 end 圆弧
        mOutPaint.strokeCap = Paint.Cap.ROUND
        canvas?.drawArc(rectF, 135f, 270f, false, mOutPaint)

        //画文字
        mTextPaint.isAntiAlias = true
        mTextPaint.color = mStepTextColor
        mTextPaint.textSize = mStepTextSize.toFloat()
        //文字的x=控件的一半-文字的一半
        mTextPaint.getTextBounds(
            mCurrentStep.toString(),
            0,
            mCurrentStep.toString().length,
            textBound
        )
        val dx = measuredWidth / 2 - textBound.width() / 2
        //基线
        val fontMetricsInt = mTextPaint.fontMetricsInt
        val dy = (fontMetricsInt.bottom - fontMetricsInt.top) / 2 - fontMetricsInt.bottom
        val baseLine = measuredHeight / 2 + dy
        val textStr = mCurrentStep.toString()
        canvas?.drawText(textStr, dx.toFloat(), baseLine.toFloat(), mTextPaint)

        /**
         * 画内圆弧 数据不能写死 百分比 数据让用户设置
         */
        mInnerPaint.isAntiAlias = true
        mInnerPaint.strokeWidth = mBorderWidth
        mInnerPaint.color = mInnerColor
        mInnerPaint.style = Paint.Style.STROKE
        //设置圆弧start 和 end 圆弧
        mInnerPaint.strokeCap = Paint.Cap.ROUND
        if (mStepMax == 0) return
        val sweepAngle: Float = mCurrentStep.toFloat() / mStepMax.toFloat()
        canvas?.drawArc(rectF, 135f, sweepAngle * 270, false, mInnerPaint)
    }

    //写方法让他动起来
    //设置步数
    fun setStepMax(stepMax: Int) {
        this.mStepMax = stepMax
    }

    //设置当前步数
    fun setCurrentStep(currentStep: Int) {
        this.mCurrentStep = currentStep
        //每设置一次都要重绘,不断绘制 onDraw()
        invalidate()
    }
}